/*
 * ImageContainer.cpp
 *
 *  Created on: Aug 22, 2012
 *      Author: alberto
 */
#include "ImageContainer.h"


/* Default Constructor for ImageContainer
*    @default baseFileName: "image_list.txt"
*    @default totalImages: 0
*
*/
ImageContainer::ImageContainer(): basefileName("image_list.txt"), imageNumber(0) {

}

/* Constructor for ImageContainer. Takes the name of the file with the image names and directory as parameter
*    @default totalImages: 0
*
*    @param bf: name of the file with the image names and directory
*/
ImageContainer::ImageContainer(const string &bf): imageNumber(0) {
	basefileName = bf;
}

/* Destructor for ImageContainer.
*/
ImageContainer::~ImageContainer() {

}

/* Reads the base file defined for the image. The base file has the directory and name of each image the container
 * should read.
 */
void ImageContainer::ReadBaseFile() {
	ifstream basefile(basefileName.c_str());
	string iname;
	char cw[100];
	getcwd(cw, 100);
	string aux(cw);
	cout << "cw: " << cw << endl;
	cout << "basefile: " << basefileName << endl;
	assert(!basefile.fail()); // Asserts the file exists

	getline(basefile, imageDirectory);
	getline(basefile, iname);
	while(!basefile.eof())
	{
		imageNames.insert(imageNames.end(), imageDirectory + iname);
		getline(basefile, iname);
	}

	basefile.close();

	return;
}

/* Reads the images the container should contain. The location of each image is based on the directory and image
 * names read from the basefile.
 */
void ImageContainer::ReadImageDirectory() {

	cout << endl << "Reading Images:" << endl << endl;
	for(vector<string>::iterator name = imageNames.begin(); name != imageNames.end(); ++name){

		try{
		    cout << "Reading image: " << *name << endl;

		    Mat img = imread(*name);
		    images.insert(images.end(), img);
		}
		catch(exception& e){
			cout << "Error reading image: " << *name << endl;
		}

	}

	imageNumber = images.size();

	return;

}

/* Prints the name of each image the container should contain. For testing purposes.
 */
void ImageContainer::ListImageNames(string fname){


	if(!fname.compare("")){
	    cout << endl << "printing image names: " << endl << endl;
	    for(size_t i = 0; i != imageNames.size(); i++){

		    cout << i << " = " << getImageName(i) << endl;

	    }
	}
	else{
	    cout << endl << "printing image names to file: " << fname << endl << endl;
	    ofstream lf;
		lf.open(fname.c_str(), fstream::out);
	    for(size_t i = 0; i != imageNames.size(); i++){

	    	lf << i << "-" << getImageName(i) << endl;

	    }
	}

	return;
}

/* Prints the name of the directory where the images are. For testing purposes.
 */
void ImageContainer::ListImageDirectory() const {

	cout << endl << "printing directory name: " << endl << endl;
	cout << imageDirectory << endl;

}

/* Shows each image the imageContainer has read. For testing purposes.
 */
void ImageContainer::showReadImages() const{

	for(vector<Mat>::size_type i = 0; i < images.size(); i++){
		imshow("image", images[i]);
		moveWindow("image", 150, 100);
		waitKey(0);
		//destroyWindow("image");
	}
	destroyAllWindows();
}

/* Gets the image with index 'idx'.
 */
Mat ImageContainer::getImages(const size_t idx) const{
	return images[idx];
}

/* Gets the path of the image with index 'idx'.
 */
string ImageContainer::getImagePath(const size_t idx) const{

	return imageNames[idx];
}

/* Gets the name of the image with index 'idx'.
 */
string ImageContainer::getImageName(const size_t idx) const{

	string name;
	size_t pos;

	pos = imageNames[idx].find_last_of("/");

	name = imageNames[idx].substr(pos+1, imageNames[idx].size());

	return name;
}

/* Gets the number of images stored.
 */
size_t ImageContainer::getImageNumber(){
	return imageNumber;
}


